iT邦幫忙

2026 iThome 鐵人賽

DAY 13
0
AI Engineering

30 天打造 AI 後端:從 LLM、RAG 到 AI Agent系列 第 13

[Day 13] 向量資料庫實際操作 — Qdrant 與 pgvector

  • 分享至 

  • xImage
  •  

延續前幾天的向量資料庫理論,今天動手實作。分別用 Qdrant(原生向量資料庫)跟 pgvector(PostgreSQL 擴充套件)跑一次完整流程:安裝 → 建立 collection/table → 寫入向量 → 查詢 → 加上 Metadata Filtering。

Part 1:Qdrant 實作

  1. 啟動 Qdrant(用 Docker 最快)

    docker run -p 6333:6333 -p 6334:6334 qdrant/qdrant
    

    啟動後可以打開 http://localhost:6333/dashboard 看到管理介面。

  2. 安裝 Python SDK

    pip install qdrant-client
    
  3. 建立 Collection

    Qdrant 的「collection」概念類似關聯式資料庫的 table,但存的是向量。

    from qdrant_client import QdrantClient
    from qdrant_client.models import Distance, VectorParams
    
    client = QdrantClient(url="http://localhost:6333")
    
    client.create_collection(
        collection_name="my_documents",
        vectors_config=VectorParams(size=768, distance=Distance.COSINE)
            # size 要跟你的 Embedding 模型輸出維度一致
        #distance 可選 COSINE / EUCLID / DOT
    )
    
  4. 寫入向量(含 Metadata)

    from qdrant_client.models import PointStruct
    
    points = [
        PointStruct(
            id=1,
            vector=[0.05, 0.61, 0.76, ...],  # 你的 embedding 結果
            payload={"text": "向量資料庫適合語意搜尋", "category": "database", "year": 2024}
        ),
        PointStruct(
            id=2,
            vector=[0.19, 0.81, 0.75, ...],
            payload={"text": "PostgreSQL 是關聯式資料庫", "category": "database", "year": 2023}
        ),
    ]
    
    client.upsert(collection_name="my_documents", points=points)
    
  5. 查詢(找最相似的向量)

    query_vector = [0.05, 0.60, 0.75, ...]  # 使用者問題轉成的向量
    
    results = client.query_points(
        collection_name="my_documents",
        query=query_vector,
        limit=3
    )
    
    for point in results.points:
        print(point.score, point.payload)
    
  6. 加上 Metadata Filtering
    比如「只搜尋 2024 年之後、且分類是 database 的資料」:

    from qdrant_client.models import Filter, FieldCondition, MatchValue, Range
    
    results = client.query_points(
        collection_name="my_documents",
        query=query_vector,
        query_filter=Filter(
            must=[
                FieldCondition(key="category", match=MatchValue(value="database")),
                FieldCondition(key="year", range=Range(gte=2024))
            ]
        ),
        limit=3
    )
    

Part 2:pgvector 實作

適合已經有 PostgreSQL 環境、不想再多引入一套系統的情況。

  1. 安裝擴充套件

    CREATE EXTENSION IF NOT EXISTS vector;
    

    (若用 Docker,可以直接用官方映像檔 pgvector/pgvector:pg16)

  2. 建立資料表

    CREATE TABLE documents (
        id SERIAL PRIMARY KEY,
        content TEXT,
        category TEXT,
        created_year INT,
        embedding VECTOR(768)  -- 維度需與你的 Embedding 模型一致
    );
    
  3. 建立索引(加速查詢,等同於 HNSW)

    CREATE INDEX ON documents
    USING hnsw (embedding vector_cosine_ops);
    

    pgvector 也支援 vector_l2_ops(歐氏距離)跟 vector_ip_ops(內積),依需求選擇。

  4. 寫入資料

    INSERT INTO documents (content, category, created_year, embedding)
    VALUES ('向量資料庫適合語意搜尋', 'database', 2024, '[0.05, 0.61, 0.76, ...]');
    

    Python 端也可以用 psycopg2 或 SQLAlchemy 批次寫入。

  5. 查詢最相似的資料

    SELECT content, category, 1 - (embedding <=> '[0.05, 0.60, 0.75, ...]') AS similarity
    FROM documents
    ORDER BY embedding <=> '[0.05, 0.60, 0.75, ...]'
    LIMIT 3;
    

    <=> 是 pgvector 的餘弦距離運算子(距離越小越相似,所以用 1 - 轉成相似度好理解)。

  6. 加上 Metadata Filtering

    SELECT content, category, created_year
    FROM documents
    WHERE category = 'database' AND created_year >= 2024
    ORDER BY embedding <=> '[0.05, 0.60, 0.75, ...]'
    LIMIT 3;
    
情境 Qdrant pgvector
查詢語法 專用 Python/REST API 標準 SQL
Metadata Filtering 需用 Filter/FieldCondition 物件 直接 WHERE 子句
部署 需獨立服務(Docker/雲端) 掛在既有 PostgreSQL 上
適合情境 專案獨立、追求效能 已有 PostgreSQL 基礎設施

上一篇
[Day 12] 向量資料庫大亂鬥
下一篇
[Day 14] 我前六天在優化錯的東西:top-1 命中 10/15,答案卻對了 15/15
系列文
30 天打造 AI 後端:從 LLM、RAG 到 AI Agent26
圖片
  熱門推薦
圖片
{{ item.channelVendor }} | {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言